package com.csu.common.handler;

import java.io.IOException;
import java.lang.reflect.Method;
import java.sql.SQLException;
import java.util.HashMap;
import java.util.Map;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.httpclient.HttpException;
import org.apache.log4j.Logger;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.method.HandlerMethod;
import org.springframework.web.servlet.HandlerExceptionResolver;
import org.springframework.web.servlet.ModelAndView;
import org.springframework.web.servlet.view.json.MappingJackson2JsonView;

import com.csu.common.constants.SystemCode;
import com.csu.common.exception.WebException;

/**
 * @项目名称：watch_mark
 * @类名称：GlobalExceptionHandler
 * @类描述：全局异常拦截处理
 * @创建人：TangC
 * @创建时间：2015-7-30 上午10:32:40
 */
public class GlobalExceptionHandler implements HandlerExceptionResolver
{

    private static Logger LOGGER = Logger.getLogger(GlobalExceptionHandler.class);

    public ModelAndView resolveException(HttpServletRequest request, HttpServletResponse response, Object handler,
            Exception ex)
    {
        // 映射具体的错误码信息
        String code = SystemCode.UNKNOWN_EXCEPTION;

        if (ex instanceof WebException)
        {
            code = ((WebException) ex).getCode();

            LOGGER.error(ex.getMessage(), ex);
        }
        else
        {
            if (ex instanceof RuntimeException)
            {
                code = SystemCode.RUNTIME_EXCEPTION;
            }
            else if (ex instanceof IOException)
            {
                code = SystemCode.IO_EXCEPTION;
            }
            else if (ex instanceof SQLException)
            {
                code = SystemCode.DATABASE_EXCEPTION;
            }
            else if (ex instanceof HttpException)
            {
                code = SystemCode.HTTP_EXCEPTION;
            }
            // 打印异常的堆栈信息到log4j
            LOGGER.error(ex.getMessage(), ex);
        }
        ModelAndView mav = new ModelAndView();

        Method requestMethod = ((HandlerMethod) handler).getMethod();

        /*
         * 方法被ResponseBody注解修饰，则返回非页面的结果。
         */
        if (requestMethod.isAnnotationPresent(ResponseBody.class))
        {
            MappingJackson2JsonView view = new MappingJackson2JsonView();

            Map<String, Object> resultPojo = new HashMap<String, Object>();

            resultPojo.put("code", code);

            /**
             * ex.toString()： 获得异常种类和错误信息 ex.getMessage():获得错误信息
             */
            resultPojo.put("desc", ex.getMessage());

            view.setAttributesMap(resultPojo);

            mav.setView(view);
        }
        else
        {
            /**
             * 可将异常信息显示到页面上！
             */
            request.setAttribute("desc", ex.getMessage());

            mav.setViewName("error");
        }
        return mav;
    }
}
